home *** CD-ROM | disk | FTP | other *** search
/ OpenGL Superbible (2nd Edition) / OpenGL SuperBible e2.iso / tools / OpenGL / OPENGL2.EXE / _SETUP.1 / wglinfo.c < prev   
Encoding:
C/C++ Source or Header  |  1997-10-31  |  11.7 KB  |  379 lines

  1. /*
  2.     wglinfo.c
  3.     Nate Robins, 1997
  4.  
  5.     Shows a graph of all the visuals that support OpenGL and their
  6.     capabilities.  Just like (well, almost) glxinfo on SGI's.
  7.     Only the -v (verbose) and -h (help) command line arguments are
  8.     implemented.
  9.  
  10.  
  11.     A legend for the table that this baby spits out
  12.         -----------------------------------------------
  13.  
  14.     visual ~= pixel format descriptor
  15.     id      = pixel format number (integer from 1 - max pixel formats)
  16.     dep     = cColorBits      - color depth
  17.     xsp     = no analog       - transparent pixel (currently always ".")
  18.     bfsz    = cColorBits      - framebuffer size (no analog in Win32?)
  19.     lvl     = bReserved       - overlay(>0), underlay(<0), main plane(0).
  20.     rgci    = iPixelType      - rb = rgba mode, ci = color index mode.
  21.     db      = dwFlags & PFD_DOUBLEBUFFER - double buffer flag (y = yes)
  22.     stro    = dwFlags & PFD_STEREO       - stereo flag        (y = yes)
  23.     rsz     = cRedBits        - # bits of red
  24.     gsz     = cGreenBits      - # bits of green
  25.     bsz     = cBlueBits       - # bits of blue
  26.     asz     = cAlphaBits      - # bits of alpha
  27.     axbf    = cAuxBuffers     - # of aux buffers
  28.     dpth    = cDepthBits      - # bits of depth
  29.     stcl    = cStencilBits    - # bits of stencil
  30.     accum r = cAccumRedBits   - # bits of red in accumulation buffer
  31.     accum g = cAccumGreenBits - # bits of green in accumulation buffer
  32.     accum b = cAccumBlueBits  - # bits of blue in accumulation buffer
  33.     accum a = cAccumAlphaBits - # bits of alpha in accumulation buffer
  34.     ms      = no analog  - multisample buffers
  35.  
  36.  */
  37.  
  38. #include <windows.h>            /* must include this before GL/gl.h */
  39. #include <GL/gl.h>            /* OpenGL header file */
  40. #include <GL/glu.h>            /* OpenGL utilities header file */
  41. #include <stdio.h>
  42.  
  43. void
  44. VisualInfo(HDC hDC, int verbose)
  45. {
  46.     int i, maxpf;
  47.     PIXELFORMATDESCRIPTOR pfd;
  48.  
  49.     /* calling DescribePixelFormat() with NULL args return maximum
  50.        number of pixel formats */
  51.     maxpf = DescribePixelFormat(hDC, 0, 0, NULL);
  52.  
  53.     if (!verbose) {
  54.  printf("   visual  x  bf lv rg d st  r  g  b a  ax dp st accum buffs  ms \n");
  55.  printf(" id dep cl sp sz l  ci b ro sz sz sz sz bf th cl  r  g  b  a ns b\n");
  56.  printf("-----------------------------------------------------------------\n");
  57.  
  58.     /* loop through all the pixel formats */
  59.     for(i = 1; i <= maxpf; i++) {
  60.  
  61.     DescribePixelFormat(hDC, i, sizeof(PIXELFORMATDESCRIPTOR), &pfd);
  62.  
  63.     /* only describe this format if it supports OpenGL */
  64.     if(!(pfd.dwFlags & PFD_SUPPORT_OPENGL))
  65.         continue;
  66.  
  67.     /* other criteria could be tested here for actual pixel format
  68.            choosing in an application:
  69.        
  70.        for (...each pixel format...) {
  71.  
  72.          if (pfd.dwFlags & PFD_SUPPORT_OPENGL &&
  73.              pfd.dwFlags & PFD_DOUBLEBUFFER &&
  74.              pfd.cDepthBits >= 24 &&
  75.              pfd.cColorBits >= 24)
  76.              {
  77.                 goto found;
  78.                  }
  79.            }
  80.        ... not found so exit ...
  81.         
  82.            found:
  83.        ... found so use it ...
  84.     */
  85.  
  86.     /* print out the information for this pixel format */
  87.     printf("0x%02x ", i);
  88.  
  89.     printf("%2d ", pfd.cColorBits);
  90.     if(pfd.dwFlags & PFD_DRAW_TO_WINDOW)      printf("wn ");
  91.     else if(pfd.dwFlags & PFD_DRAW_TO_BITMAP) printf("bm ");
  92.     else printf(".  ");
  93.  
  94.     /* should find transparent pixel from LAYERPLANEDESCRIPTOR */
  95.     printf(" . "); 
  96.  
  97.     printf("%2d ", pfd.cColorBits);
  98.  
  99.     /* bReserved field indicates number of over/underlays */
  100.     if(pfd.bReserved) printf(" %d ", pfd.bReserved);
  101.     else printf(" . "); 
  102.  
  103.     printf(" %c ", pfd.iPixelType == PFD_TYPE_RGBA ? 'r' : 'c');
  104.  
  105.     printf("%c ", pfd.dwFlags & PFD_DOUBLEBUFFER ? 'y' : '.');
  106.  
  107.     printf(" %c ", pfd.dwFlags & PFD_STEREO ? 'y' : '.');
  108.  
  109.     if(pfd.cRedBits && pfd.iPixelType == PFD_TYPE_RGBA) 
  110.         printf("%2d ", pfd.cRedBits);
  111.     else printf(" . ");
  112.  
  113.     if(pfd.cGreenBits && pfd.iPixelType == PFD_TYPE_RGBA) 
  114.         printf("%2d ", pfd.cGreenBits);
  115.     else printf(" . ");
  116.  
  117.     if(pfd.cBlueBits && pfd.iPixelType == PFD_TYPE_RGBA) 
  118.         printf("%2d ", pfd.cBlueBits);
  119.     else printf(" . ");
  120.  
  121.     if(pfd.cAlphaBits && pfd.iPixelType == PFD_TYPE_RGBA) 
  122.         printf("%2d ", pfd.cAlphaBits);
  123.     else printf(" . ");
  124.  
  125.     if(pfd.cAuxBuffers)     printf("%2d ", pfd.cAuxBuffers);
  126.     else printf(" . ");
  127.  
  128.     if(pfd.cDepthBits)      printf("%2d ", pfd.cDepthBits);
  129.     else printf(" . ");
  130.  
  131.     if(pfd.cStencilBits)    printf("%2d ", pfd.cStencilBits);
  132.     else printf(" . ");
  133.  
  134.     if(pfd.cAccumRedBits)   printf("%2d ", pfd.cAccumRedBits);
  135.     else printf(" . ");
  136.  
  137.     if(pfd.cAccumGreenBits) printf("%2d ", pfd.cAccumGreenBits);
  138.     else printf(" . ");
  139.  
  140.     if(pfd.cAccumBlueBits)  printf("%2d ", pfd.cAccumBlueBits);
  141.     else printf(" . ");
  142.  
  143.     if(pfd.cAccumAlphaBits) printf("%2d ", pfd.cAccumAlphaBits);
  144.     else printf(" . ");
  145.  
  146.     /* no multisample in Win32 */
  147.     printf(" . .\n");
  148.     }
  149.  
  150.     /* print table footer */
  151.  printf("-----------------------------------------------------------------\n");
  152.  printf("   visual  x  bf lv rg d st  r  g  b a  ax dp st accum buffs  ms \n");
  153.  printf(" id dep cl sp sz l  ci b ro sz sz sz sz bf th cl  r  g  b  a ns b\n");
  154.  printf("-----------------------------------------------------------------\n");
  155.  
  156.     } else {                /* verbose output. */
  157.     /* loop through all the pixel formats */
  158.     for(i = 1; i <= maxpf; i++) {
  159.         
  160.         DescribePixelFormat(hDC, i, sizeof(PIXELFORMATDESCRIPTOR), &pfd);
  161.         
  162.         /* only describe this format if it supports OpenGL */
  163.         if(!(pfd.dwFlags & PFD_SUPPORT_OPENGL))
  164.         continue;
  165.  
  166.         printf("Visual ID: %2d  depth=%d  class=%s\n", i, pfd.cDepthBits, 
  167.            pfd.cColorBits <= 8 ? "PseudoColor" : "TrueColor");
  168.         printf("    bufferSize=%d level=%d renderType=%s doubleBuffer=%d stereo=%d\n", pfd.cColorBits, pfd.bReserved, pfd.iPixelType == PFD_TYPE_RGBA ? "rgba" : "ci", pfd.dwFlags & PFD_DOUBLEBUFFER, pfd.dwFlags & PFD_STEREO);
  169.         printf("    rgba: redSize=%d greenSize=%d blueSize=%d alphaSize=%d\n", pfd.cRedBits, pfd.cGreenBits, pfd.cBlueBits, pfd.cAlphaBits);
  170.         printf("    auxBuffers=%d depthSize=%d stencilSize=%d\n", pfd.cAuxBuffers, pfd.cDepthBits, pfd.cStencilBits);
  171.         printf("    accum: redSize=%d greenSize=%d blueSize=%d alphaSize=%d\n", pfd.cAccumRedBits, pfd.cAccumGreenBits, pfd.cAccumBlueBits, pfd.cAccumAlphaBits);
  172.         printf("    multiSample=%d multisampleBuffers=%d\n", 0, 0);
  173.         printf("    Opaque.\n");
  174.     }
  175.     }
  176. }
  177.  
  178. LONG WINAPI
  179. WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
  180.     static PAINTSTRUCT ps;
  181.  
  182.     switch(uMsg) {
  183.     case WM_PAINT:
  184.     BeginPaint(hWnd, &ps);
  185.     EndPaint(hWnd, &ps);
  186.     return 0;
  187.  
  188.     case WM_SIZE:
  189.     glViewport(0, 0, LOWORD(lParam), HIWORD(lParam));
  190.     PostMessage(hWnd, WM_PAINT, 0, 0);
  191.     return 0;
  192.  
  193.     case WM_CHAR:
  194.     switch (wParam) {
  195.     case 27:            /* ESC key */
  196.         PostQuitMessage(0);
  197.         break;
  198.     }
  199.     return 0;
  200.  
  201.     case WM_CLOSE:
  202.     PostQuitMessage(0);
  203.     return 0;
  204.     }
  205.  
  206.     return DefWindowProc(hWnd, uMsg, wParam, lParam); 
  207.  
  208. HWND
  209. CreateOpenGLWindow(char* title, int x, int y, int width, int height, 
  210.            BYTE type, DWORD flags)
  211. {
  212.     int         pf;
  213.     HDC         hDC;
  214.     HWND        hWnd;
  215.     WNDCLASS    wc;
  216.     PIXELFORMATDESCRIPTOR pfd;
  217.     static HINSTANCE hInstance = 0;
  218.  
  219.     /* only register the window class once - use hInstance as a flag. */
  220.     if (!hInstance) {
  221.     hInstance = GetModuleHandle(NULL);
  222.     wc.style         = CS_OWNDC;
  223.     wc.lpfnWndProc   = (WNDPROC)WindowProc;
  224.     wc.cbClsExtra    = 0;
  225.     wc.cbWndExtra    = 0;
  226.     wc.hInstance     = hInstance;
  227.     wc.hIcon         = LoadIcon(NULL, IDI_WINLOGO);
  228.     wc.hCursor       = LoadCursor(NULL, IDC_ARROW);
  229.     wc.hbrBackground = NULL;
  230.     wc.lpszMenuName  = NULL;
  231.     wc.lpszClassName = "OpenGL";
  232.  
  233.     if (!RegisterClass(&wc)) {
  234.         MessageBox(NULL, "RegisterClass() failed:  "
  235.                "Cannot register window class.", "Error", MB_OK);
  236.         return NULL;
  237.     }
  238.     }
  239.  
  240.     hWnd = CreateWindow("OpenGL", title, WS_OVERLAPPEDWINDOW |
  241.             WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
  242.             x, y, width, height, NULL, NULL, hInstance, NULL);
  243.  
  244.     if (hWnd == NULL) {
  245.     MessageBox(NULL, "CreateWindow() failed:  Cannot create a window.",
  246.            "Error", MB_OK);
  247.     return NULL;
  248.     }
  249.  
  250.     hDC = GetDC(hWnd);
  251.  
  252.     /* there is no guarantee that the contents of the stack that become
  253.        the pfd are zeroed, therefore _make sure_ to clear these bits. */
  254.     memset(&pfd, 0, sizeof(pfd));
  255.     pfd.nSize        = sizeof(pfd);
  256.     pfd.nVersion     = 1;
  257.     pfd.dwFlags      = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | flags;
  258.     pfd.iPixelType   = type;
  259.     pfd.cColorBits   = 32;
  260.  
  261.     pf = ChoosePixelFormat(hDC, &pfd);
  262.     if (pf == 0) {
  263.     MessageBox(NULL, "ChoosePixelFormat() failed:  "
  264.            "Cannot find a suitable pixel format.", "Error", MB_OK); 
  265.     return 0;
  266.     } 
  267.  
  268.     if (SetPixelFormat(hDC, pf, &pfd) == FALSE) {
  269.     MessageBox(NULL, "SetPixelFormat() failed:  "
  270.            "Cannot set format specified.", "Error", MB_OK);
  271.     return 0;
  272.     } 
  273.  
  274.     DescribePixelFormat(hDC, pf, sizeof(PIXELFORMATDESCRIPTOR), &pfd);
  275.  
  276.     ReleaseDC(hDC, hWnd);
  277.  
  278.     return hWnd;
  279. }    
  280.  
  281. int 
  282. main(int argc, char** argv)
  283. {
  284.     HDC hDC;                /* device context */
  285.     HGLRC hRC;                /* opengl context */
  286.     HWND  hWnd;                /* window */
  287.     MSG   msg;                /* message */
  288.     int   i;
  289.     char* s;
  290.     char  t[80];
  291.     char* p;
  292.     int verbose = 0;
  293.  
  294.     while (--argc) {
  295.     if (strcmp("-h", argv[argc]) == 0) {
  296.         printf("Usage: wglinfo [-v] [-t] [-m] [-h] [-dispay <dname>] [-nfbc] [-fpcinfo]\n");
  297.         printf("        -v: Print visuals info in verbose form.\n");
  298.         printf("        -t: Print verbose table (not implemented on Win32)\n");
  299.         printf("        -m: Don't print mid table headers (in long tables). (not on Win32)\n");
  300.         printf("        -display <dname>: Print GLX visuals on specified server. (not on Win32)\n");
  301.         printf("        -nfbc: Don't use fbconfig extension (not available on Win32)\n");
  302.         printf("        -fbcinfo: print out additional fbconfig information (not on Win32)\n");
  303.         printf("        -h: This screen.\n");
  304.         exit(0);
  305.     } else if (strcmp("-v", argv[argc]) == 0) {
  306.         verbose = 1;
  307.     }
  308.     }
  309.  
  310.     hWnd = CreateOpenGLWindow("wglinfo", 0, 0, 100, 100, PFD_TYPE_RGBA, 0);
  311.     if (hWnd == NULL)
  312.     exit(1);
  313.  
  314.     hDC = GetDC(hWnd);
  315.     hRC = wglCreateContext(hDC);
  316.     wglMakeCurrent(hDC, hRC);
  317.  
  318.     ShowWindow(hWnd, SW_HIDE);
  319.  
  320.     /* output header information */
  321.     printf("display: N/A\n");
  322.     printf("server wgl vendor string: N/A\n");
  323.     printf("server wgl version string: N/A\n");
  324.     printf("server wgl extensions (WGL_): N/A\n");
  325.     printf("client wgl version: N/A\n");
  326.     printf("client wgl extensions (WGL_): none\n");
  327.     printf("OpenGL vendor string: %s\n", glGetString(GL_VENDOR));
  328.     printf("OpenGL renderer string: %s\n", glGetString(GL_RENDERER));
  329.     printf("OpenGL version string: %s\n", glGetString(GL_VERSION));
  330.     printf("OpenGL extensions (GL_): \n");
  331.  
  332.     /* do the magic to separate all extensions with comma's, except
  333.        for the last one that _may_ terminate in a space. */
  334.     i = 0;
  335.     s = (char*)glGetString(GL_EXTENSIONS);
  336.     t[79] = '\0';
  337.     while(*s) {
  338.     t[i++] = *s;
  339.     if(*s == ' ') {
  340.         if (*(s+1) != '\0') {
  341.         t[i-1] = ',';
  342.         t[i] = ' ';
  343.         p = &t[i++];
  344.         } else {           /* zoinks! last one terminated in a space! */
  345.         t[i-1] = '\0';
  346.         }
  347.     }
  348.     if(i > 80 - 5) {
  349.         *p = t[i] = '\0';
  350.         printf("    %s\n", t);
  351.         p++;
  352.         i = strlen(p);
  353.         strcpy(t, p);
  354.     }
  355.     s++;
  356.     }
  357.     t[i] = '\0';
  358.     printf("    %s.\n\n", t);
  359.  
  360.     /* enumerate all the formats */
  361.     VisualInfo(hDC, verbose);
  362.  
  363.     PostQuitMessage(0);
  364.     while(GetMessage(&msg, hWnd, 0, 0)) {
  365.     TranslateMessage(&msg);
  366.     DispatchMessage(&msg);
  367.     }
  368.  
  369.     wglMakeCurrent(NULL, NULL);
  370.     ReleaseDC(hDC, hWnd);
  371.     wglDeleteContext(hRC);
  372.     DestroyWindow(hWnd);
  373.  
  374.     return msg.wParam;
  375. }
  376. 
  377.